Skip to content

feat(prometheus): add metrics for AI cache hits, misses, bypasses, and embedding latency - #13659

Merged
nic-6443 merged 4 commits into
apache:masterfrom
janiussyafiq:feat/ai-cache-prometheus-metrics
Jul 7, 2026
Merged

feat(prometheus): add metrics for AI cache hits, misses, bypasses, and embedding latency#13659
nic-6443 merged 4 commits into
apache:masterfrom
janiussyafiq:feat/ai-cache-prometheus-metrics

Conversation

@janiussyafiq

@janiussyafiq janiussyafiq commented Jul 3, 2026

Copy link
Copy Markdown
Contributor

Description

Adds Prometheus metrics for the ai-cache plugin (#13578, #13632, #13644), integrated in prometheus/exporter.lua following the existing llm_* metric pattern:

  • apisix_ai_cache_hits_total (with layer="exact"|"semantic"), apisix_ai_cache_misses_total, apisix_ai_cache_bypasses_total — counters sharing the llm_* label set (route_id, service_id, consumer, node, request_type, request_llm_model, llm_model)
  • apisix_ai_cache_embedding_latency — histogram of embedding-call latency in milliseconds (the issue sketched _seconds, but the exporter's latency histograms use milliseconds with DEFAULT_BUCKETS, so this follows the house convention)

Semantics: Redis fail-open lookups count as MISS; fail_mode: error rejections record nothing; recording happens in log phase and is a silent no-op when the prometheus plugin is disabled. Docs: label sections added to prometheus.md (en + zh).

Which issue(s) this PR fixes:

Fixes #13290

Checklist

  • I have explained the need for this PR and the problem it solves
  • I have explained the changes or the new features added to this PR
  • I have added tests corresponding to this change
  • I have updated the documentation to reflect this change
  • I have verified that this change is backward compatible (If not, please discuss on the APISIX mailing list first)

@dosubot dosubot Bot added size:XL This PR changes 500-999 lines, ignoring generated files. enhancement New feature or request labels Jul 3, 2026
Comment thread apisix/plugins/prometheus/exporter.lua Outdated
metrics[name]:inc(1,
get_enabled_label_values_for_metric(name, disabled_label_metric_map,
layer or "exact", route_id, service_id, consumer_name, balancer_ip,
vars.request_type, vars.request_llm_model, vars.llm_model,

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Refer to this PR: #13637

As the model name is from Client, I suggest we should also limit the Maximum length 🤔

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed

Comment thread docs/en/latest/plugins/prometheus.md Outdated
| route_id | ID of the Route that the metric corresponds to. Default to an empty string if a request does not match any Route. |
| service_id | ID of the Service that the matched Route belongs to. Default to an empty string if the matched Route does not belong to any Service. |
| consumer | Name of the Consumer associated with a request. Default to an empty string if no Consumer is associated with the request. |
| node | IP address of the upstream node. Empty for requests served from the cache, which never reach the upstream. |

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

??

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same problem as below?

Comment thread docs/en/latest/plugins/prometheus.md Outdated
| node | IP address of the upstream node. Empty for requests served from the cache, which never reach the upstream. |
| request_type | traditional_http / ai_chat / ai_stream |
| request_llm_model | Model name requested by the client. |
| llm_model | Model name reported by the LLM response. Empty for requests served from the cache, which never reach the upstream. |

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How to understand "Empty for requests served from the cache, which never reach the upstream. "?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Since the requests is served from cache, meaning we never called the upstream to get the response back hence empty. Should i reword this or still shows the model neverthelesss?

@dosubot dosubot Bot added size:L This PR changes 100-499 lines, ignoring generated files. and removed size:XL This PR changes 500-999 lines, ignoring generated files. labels Jul 6, 2026
membphis
membphis previously approved these changes Jul 6, 2026

@membphis membphis left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM. No merge-blocking issues found in the review.

nic-6443
nic-6443 previously approved these changes Jul 6, 2026
Comment thread apisix/plugins/ai-cache.lua Outdated
Comment on lines +318 to +323
if ctx.ai_cache_status then
exporter.inc_ai_cache_status(ctx, ctx.ai_cache_status, ctx.ai_cache_hit_layer)
end
if ctx.ai_cache_embedding_latency then
exporter.observe_ai_cache_embedding_latency(ctx, ctx.ai_cache_embedding_latency)
end

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

all values passed to these functions are in the ctx table, so why can't we directly call these functions in the exporter module directly?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

agreed, that'd be cleaner. fixed

@janiussyafiq
janiussyafiq dismissed stale reviews from nic-6443 and membphis via 16c2c53 July 6, 2026 08:45
@nic-6443
nic-6443 requested a review from membphis July 7, 2026 02:23

@membphis membphis left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code review passed; no blocking issues found.

@nic-6443
nic-6443 merged commit d0c3cee into apache:master Jul 7, 2026
19 checks passed
@janiussyafiq
janiussyafiq deleted the feat/ai-cache-prometheus-metrics branch July 7, 2026 03:13
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

enhancement New feature or request size:L This PR changes 100-499 lines, ignoring generated files.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

feat: add ai-cache plugin for LLM semantic caching

5 participants